package com.zmj.sy.mom.srv.aps.utils.nest;

import cn.hutool.core.collection.CollUtil;
import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.zmj.sy.mom.srv.aps.bean.dto.feign.Ltk.LtkPushTokenDto;
import com.zmj.sy.mom.srv.aps.bean.entity.base.BaseEntity;
import com.zmj.sy.mom.srv.aps.bean.entity.lantekpre.*;
import com.zmj.sy.mom.srv.aps.bean.entity.order.*;
import com.zmj.sy.mom.srv.aps.bean.entity.resource.Factory;
import com.zmj.sy.mom.srv.aps.bean.entity.resource.PlateStandard;
import com.zmj.sy.mom.srv.aps.bean.vo.lantek.LantekReceiveNestNestReqVo;
import com.zmj.sy.mom.srv.aps.bean.vo.lantek.LantekReceiveNestPartReqVo;
import com.zmj.sy.mom.srv.aps.bean.vo.lantek.LantekReceiveNestReqVo;
import com.zmj.sy.mom.srv.aps.bean.vo.nest.NestLanCommonsResVo;
import com.zmj.sy.mom.srv.aps.bean.vo.nest.NestReceiveReqVo;
import com.zmj.sy.mom.srv.aps.bean.vo.nestpre.*;
import com.zmj.sy.mom.srv.aps.feign.LantekPreApiClient;
import com.zmj.sy.mom.srv.aps.mapper.*;
import com.zmj.sy.mom.srv.aps.utils.*;
import lombok.RequiredArgsConstructor;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;

import java.math.BigDecimal;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

@RequiredArgsConstructor
@Slf4j
@Component
public class LantekPreNestRule extends DefaultNestRule {

    private final ApsOrderMapper apsOrderMapper;

    private final ApsWorkOrderMapper apsWorkOrderMapper;

    private final OrderBomMapper orderBomMapper;

    private final FactoryMapper factoryMapper;

    private final OrderMapper orderMapper;

    private final OrderPartMapper orderPartMapper;

    private final PlateStandardMapper plateStandardMapper;

    private final LantekPreApiClient lantekPreApiClient;

    private final LantekPushDrawMapper lantekPushDrawMapper;

    private final LantekPushPlanMapper lantekPushPlanMapper;

    private final ObjectMapper objectMapper;

    private final LantekNestNestMapper lantekNestNestMapper;

    private final LantekNestPartMapper lantekNestPartMapper;

    private final LantekNestPlateMapper lantekNestPlateMapper;

    private final LantekNestExcessMapper lantekNestExcessMapper;

    private final LantekNestMoveMapper lantekNestMoveMapper;

    private final ImportMbdDxfMapper importMbdDxfMapper;
    private final ApsWorkDetailMapper apsWorkDetailMapper;
    private final LantekPushPackageMapper lantekPushPackageMapper;

    @Value("${project.feign.dxf-download}")
    private String dxfDownload;

    @Override
    public String getCode() {
        return NestRule.LANTEK_PRE;
    }

    @Override
    public boolean isPre() {
        return getCode().split(":")[1].equals("1");
    }

    @Override
    public String getSource() {
        return getCode().split(":")[0];
    }

    @Override
    @Transactional(propagation = Propagation.REQUIRES_NEW)
    public void partAdd(List<OrderBom> orderBomList) {

        List<OrderBom> collect = orderBomList.stream().map(e -> {
            OrderBom ob = MkBeanUtils.copyProperties(e, OrderBom.class);
            if (ob.getPlmId().endsWith("_170")) {
                ob.setPlmId(ob.getPlmId().replace("_170", ""));
            }
            return ob;
        }).collect(Collectors.toList());

        Collection<OrderBom> values = orderBomList.stream().collect(Collectors.toMap(e -> e.getPlmId(), Function.identity(), (e1, e2) -> e1)).values();

        List<ImportMbdDxf> mbdDxfList = importMbdDxfMapper.lambdaQuery()
                .in(ImportMbdDxf::getPlmid, collect.stream().map(OrderBom::getPlmId).collect(Collectors.toList()))
                .orderByDesc(ImportMbdDxf::getDocVersion)
                .list();
        Map<String, List<ImportMbdDxf>> mbdDxfMap = mbdDxfList.stream().collect(Collectors.groupingBy(ImportMbdDxf::getPlmid));

        List<LantekPushDraw> lantekPushDrawList = lantekPushDrawMapper.lambdaQuery()
                .in(LantekPushDraw::getPartId, orderBomList.stream().map(OrderBom::getPlmId).collect(Collectors.toList()))
                .list();
        Map<String, List<LantekPushDraw>> lantekPushDrawMap = lantekPushDrawList.stream().collect(Collectors.groupingBy(LantekPushDraw::getPartId));

        // 获取工厂信息
        List<Factory> factoryList = factoryMapper.selectList(null);
        Map<Integer, Factory> factoryMap = factoryList.stream().collect(Collectors.toMap(BaseEntity::getId, Function.identity()));

        List<LantekPushDraw> lantekPushDraws = new ArrayList<>();

        for (OrderBom orderBom : values) {
            List<LantekPushDraw> lantekPushDrawsPart = lantekPushDrawMap.get(orderBom.getPlmId());
            if (CollUtil.isNotEmpty(lantekPushDrawsPart)) {
                continue;
            }
            List<ImportMbdDxf> partDxfList = mbdDxfMap.get(orderBom.getPlmId().replace("_170", ""));

            String standard = orderBom.getStandards();
            String[] split = standard.split("δ");

            String factoryIdk = factoryMap.get(orderBom.getFactoryId()).getMyCode();

            LantekPushDraw pushDraw = new LantekPushDraw();
            pushDraw.setFactoryIdk(factoryIdk);
            pushDraw.setNorm(orderBom.getStandards());
            pushDraw.setPartId(orderBom.getPlmId());
            pushDraw.setPartName(orderBom.getMaterName());
            pushDraw.setPartType(1);
            pushDraw.setPushType(2);
            pushDraw.setVersionNum(1L);
            if (StringUtils.hasText(orderBom.getTexture())) {
                pushDraw.setTexture(orderBom.getTexture());
            } else {
                pushDraw.setTexture(split[0]);
            }
            if (orderBom.getMaterHigh() != null) {
                pushDraw.setThickness(BigDecimal.valueOf(orderBom.getMaterHigh()));
            } else {
                pushDraw.setThickness(BigDecimal.valueOf(Integer.parseInt(split[1])));
            }
            if (CollUtil.isNotEmpty(partDxfList)) {
                ImportMbdDxf partDxf = partDxfList.get(0);

                pushDraw.setFilePath(partDxf.getPath());
                pushDraw.setStatus(1);
                pushDraw.setErrorMsg(null);
                pushDraw.setUniMaterCode(orderBom.getPlmId() + "#" + partDxf.getDocVersion());
                pushDraw.setDrawVersion(partDxf.getDocVersion());
            } else {
                pushDraw.setFilePath(null);
                pushDraw.setStatus(5);
                pushDraw.setErrorMsg("缺少下料DXF图。");
                pushDraw.setUniMaterCode(orderBom.getPlmId() + "#" + "A.0");
                pushDraw.setDrawVersion("A.0");
            }

            lantekPushDraws.add(pushDraw);
        }

        if (CollUtil.isNotEmpty(lantekPushDraws)) {
            lantekPushDrawMapper.insertBatchSomeColumn(lantekPushDraws);
        }

    }

    @Override
    public void partPush() {

        try {
            fixPart();
        } catch (Exception e) {
        }

        List<LantekPushDraw> lantekPushDrawList = lantekPushDrawMapper.lambdaQuery()
                .eq(LantekPushDraw::getStatus, 1)
                .eq(LantekPushDraw::getPushType, 2)
                .list();

        List<LantekPreDrawInfoVo> pushVoList = new ArrayList<>();

        for (LantekPushDraw draw : lantekPushDrawList) {
            LantekPreDrawInfoVo vo = new LantekPreDrawInfoVo();
            vo.setUniMaterCode(draw.getUniMaterCode());
            vo.setMaterName(draw.getPartName());
            vo.setTexture(draw.getTexture());
            vo.setThickness(draw.getThickness().intValue());
            vo.setDxfPath(dxfDownload + draw.getFilePath());
            pushVoList.add(vo);
        }
        if (CollUtil.isEmpty(pushVoList)) {
            return ;
        }
        LantekPreDrawReqVo pushVo = new LantekPreDrawReqVo();
        pushVo.setParts(pushVoList);
        log.info("推送信息：{}", JsonUtils.toJsonString(pushVo));
        NestLanCommonsResVo pre = lantekPreApiClient.registerOrUpdate(pushVo, LtkPushTokenDto.TOKEN);
        log.info("推送结果：{}", JsonUtils.toJsonString(pre));
        int res = 0;
        if (pre.getCode() == 200) {
            res = 4;
        } else {
            res = 5;
        }
        for (LantekPushDraw draw : lantekPushDrawList) {
            draw.setStatus(res);
            lantekPushDrawMapper.updateById(draw);
        }

    }

    public void fixPart() {
        List<LantekPushDraw> pushDrawList = lantekPushDrawMapper.lambdaQuery().eq(LantekPushDraw::getStatus, 5).list();
        if (CollUtil.isEmpty(pushDrawList)) {
            return;
        }
        List<String> partIdList = pushDrawList.stream()
                .map(e -> {
                    if (e.getPartId().contains("_170")) {
                        return e.getPartId().replace("_170", "");
                    } else {
                        return e.getPartId();
                    }
                }).collect(Collectors.toList());
        List<ImportMbdDxf> partDxfList = importMbdDxfMapper.lambdaQuery()
                .in(ImportMbdDxf::getPlmid, partIdList)
                .list();
        Map<String, ImportMbdDxf> partDxfMap = partDxfList.stream().collect(Collectors.toMap(ImportMbdDxf::getPlmid, Function.identity()));
        for (LantekPushDraw draw : pushDrawList) {
            String partId = draw.getPartId();
            if (partId.contains("_170")) {
                partId = partId.replace("_170", "");
            }
            ImportMbdDxf mbdDxf = partDxfMap.get(partId);
            if (ObjectUtils.isEmpty(mbdDxf)) {
                continue;
            }
            draw.setFilePath(mbdDxf.getPath());
            draw.setStatus(1);
            draw.setErrorMsg("图纸已补充！");
            draw.setUniMaterCode(draw.getPartId() + "#" + mbdDxf.getDocVersion());
            draw.setDrawVersion(mbdDxf.getDocVersion());
            lantekPushDrawMapper.updateById(draw);
        }
    }

    @Override
    @Transactional(propagation = Propagation.NESTED)
    public void planAdd(List<ApsWorkDetail> detailList, List<OrderBom> bomList, Object object) {

        if (CollUtil.isEmpty(bomList)) {
            return;
        }

        LantekNewPrePlanVo reqVo = (LantekNewPrePlanVo) object;
        List<LantekNewPrePlanInfoVo> infoVoList = reqVo.getInfoVoLIst();
        Map<Integer, LantekNewPrePlanInfoVo> infoVoMap = infoVoList.stream().collect(Collectors.toMap(LantekNewPrePlanInfoVo::getId, Function.identity()));

        List<OrderBom> orderBomList = bomList;

        List<Integer> bomPidList = orderBomList.stream().map(OrderBom::getPid).collect(Collectors.toList());
        List<OrderBom> orderBomPList = orderBomMapper.lambdaQuery().in(OrderBom::getId, bomPidList).list();
        Map<Integer, OrderBom> orderBomPMap = orderBomPList.stream().collect(Collectors.toMap(BaseEntity::getId, Function.identity()));

        List<Factory> factoryList = factoryMapper.selectList(null);
        Map<Integer, Factory> factoryMap = factoryList.stream().collect(Collectors.toMap(BaseEntity::getId, Function.identity()));

        List<LantekPushDraw> lantekPushDrawList = lantekPushDrawMapper.lambdaQuery().in(LantekPushDraw::getPartId, orderBomList.stream().map(OrderBom::getPlmId).collect(Collectors.toList())).list();
        if (CollUtil.isEmpty(lantekPushDrawList)) {
            throw SyExceptionUtils.e("图纸未进行推送！");
        }
        Map<String, LantekPushDraw> lantekPushDrawMap = lantekPushDrawList.stream().collect(Collectors.toMap(LantekPushDraw::getPartId, Function.identity()));

        List<PlateStandard> plateStandardList = plateStandardMapper.lambdaQuery().in(PlateStandard::getNorm, orderBomList.stream().map(OrderBom::getStandards).distinct().collect(Collectors.toList())).list();
        Map<String, List<PlateStandard>> plateStandardMap = plateStandardList.stream().collect(Collectors.groupingBy(PlateStandard::getNorm));

        List<LantekPushPlan> pushPlanList = new ArrayList<>();
        for (OrderBom orderBom : orderBomList) {
            LantekPushPlan pushPlan = new LantekPushPlan();

            OrderBom parent = orderBomPMap.get(orderBom.getPid());

            LantekNewPrePlanInfoVo info = infoVoMap.get(orderBom.getOrderId());

            LantekPushDraw pushDraw = lantekPushDrawMap.get(orderBom.getPlmId());

            LantekPushPlan planMax = lantekPushPlanMapper.lambdaQuery().eq(LantekPushPlan::getOrderId, info.getId()).orderByDesc(LantekPushPlan::getPreVersion).last(" LIMIT 1").one();
            int preVersion = planMax == null ? 1 : planMax.getPreVersion() + 1;

            pushPlan.setComponentId(parent.getPlmId());
            pushPlan.setComponentName(parent.getMaterName());
            pushPlan.setFactoryIdk(factoryMap.get(orderBom.getFactoryId()).getMyCode());
            pushPlan.setNestPlanId(String.valueOf(orderBom.getId()));
            pushPlan.setPartId(orderBom.getPlmId());
            pushPlan.setPartName(orderBom.getMaterName());
            pushPlan.setPartType(1);
            pushPlan.setPlanAmount(orderBom.getTotalCount().multiply(BigDecimal.valueOf(info.getCount())));
            pushPlan.setProcessingNo("WP01");
            pushPlan.setProductId(reqVo.getPreNestCode());
            pushPlan.setVersionBrief("V1");
            if (ObjectUtils.isEmpty(pushDraw) || pushDraw.getStatus() == 5) {
                pushPlan.setStatus(5);
                pushPlan.setErrorMsg("推送图纸异常。");
                pushPlan.setUniMaterCode(orderBom.getPlmId() + "#A.0");
            } else {
                pushPlan.setStatus(1);
                pushPlan.setErrorMsg(null);
                pushPlan.setUniMaterCode(orderBom.getPlmId() + "#" + pushDraw.getDrawVersion());
            }
            pushPlan.setPlanFinishAmount(new BigDecimal(0));
            pushPlan.setOrderId(info.getId());
            pushPlan.setPushType(2);
            pushPlan.setVersionNum(1);
            pushPlan.setConsumeStatus(0);
            if (plateStandardMap.containsKey(orderBom.getStandards())) {
                pushPlan.setPlateLength(plateStandardMap.get(orderBom.getStandards()).get(0).getLength());
                pushPlan.setPlateWidth(plateStandardMap.get(orderBom.getStandards()).get(0).getWidth());
            } else {
                pushPlan.setPlateLength(10000);
                pushPlan.setPlateWidth(2500);
            }
            pushPlan.setPreVersion(preVersion);

            pushPlanList.add(pushPlan);
        }

        if (CollUtil.isEmpty(pushPlanList)) {
            return ;
        }
        lantekPushPlanMapper.insertBatchSomeColumn(pushPlanList);

    }

    @Override
    public void planPush(List<Integer> ids, String groupCode, Integer spaceId) {

        List<LantekPushPlan> pushPlanList = lantekPushPlanMapper.lambdaQuery()
                .in(LantekPushPlan::getId, ids)
                .eq(LantekPushPlan::getStatus, 1)
                .list();

        List<LantekPrePlanInfoVo> pushVoList = new ArrayList<>();

        for (LantekPushPlan plan : pushPlanList) {
            LantekPrePlanInfoVo vo = new LantekPrePlanInfoVo();
            vo.setPlanId(plan.getNestPlanId());
            vo.setUniMaterCode(plan.getUniMaterCode());
            vo.setConstructCode(plan.getProductId());
            vo.setAssemblyCode(plan.getComponentId());
            vo.setAssemblyName(plan.getComponentName());
            vo.setPlanAmount(plan.getPlanAmount().intValue());
            vo.setPackageCode(plan.getProcessingNo());
            vo.setPlateLength(plan.getPlateLength());
            vo.setPlateWidth(plan.getPlateWidth());
            vo.setOrderId(plan.getOrderId() + "_" + plan.getPreVersion());
            pushVoList.add(vo);
        }

        if (CollUtil.isEmpty(pushVoList)) {
            return ;
        }
        LantekPrePlanReqVo pushVo = new LantekPrePlanReqVo();
        pushVo.setOrders(pushVoList);
        log.info("推送预套料信息：{}", JsonUtils.toJsonString(pushVo));
        NestLanCommonsResVo pre = lantekPreApiClient.createPlan(pushVo, LtkPushTokenDto.TOKEN);
        log.info("推送预套料结果：{}", JsonUtils.toJsonString(pre));
        int res = 0;
        if (pre.getCode() == 200) {
            res = 4;
        } else {
            res = 5;
        }
        for (LantekPushPlan plan : pushPlanList) {
            plan.setStatus(res);
            lantekPushPlanMapper.updateById(plan);
        }

    }

    @Override
    public void platesPush(Integer spaceId, List<String> plateCodes) {

    }

    @Override
    @SneakyThrows
    @Transactional(rollbackFor = Exception.class)
    public void nestReceive(String body) {

        JavaType javaType = objectMapper.getTypeFactory().constructParametricType(List.class, LantekReceiveNestReqVo.class);
        List<LantekReceiveNestReqVo> reqVo = objectMapper.readValue(body, javaType);

        receiveNest(reqVo);

    }

    @Transactional(rollbackFor = Exception.class)
    public void receiveNest(List<LantekReceiveNestReqVo> reqVo) {

        LantekReceiveNestReqVo lantekReceiveNestReqVo = reqVo.get(0);
        List<LantekReceiveNestPartReqVo> part1 = lantekReceiveNestReqVo.getPart();
        LantekReceiveNestPartReqVo lantekReceiveNestPartReqVo = part1.get(0);
        String orderIdStr = lantekReceiveNestPartReqVo.getOrderId();
        String[] split = orderIdStr.split("_");
        int preVersion = Integer.parseInt(split[1]);

        Map<String, List<LantekNestPart>> partMap = new HashMap<>();

        for (LantekReceiveNestReqVo vo : reqVo) {

            // 套料
            LantekReceiveNestNestReqVo nest = vo.getNest();
            LantekNestNest nestEntity = MkBeanUtils.copyProperties(nest, LantekNestNest.class);
            nestEntity.setNestId(nest.getNestId());
            nestEntity.setFactoryIdk(nest.getFactoryCode());
            nestEntity.setCutLength(nest.getCutLength());
            nestEntity.setCutNozzleNorm(nest.getCutNozzleNorm());
            nestEntity.setCutNozzleNumber(nest.getCutNozzleNumber());
            nestEntity.setCutNozzleDistance(nest.getCutNozzleDistance());
            nestEntity.setWidth(nest.getWidth());
            nestEntity.setLength(nest.getLength());
            nestEntity.setNestDate(nest.getNestDateTime());
            nestEntity.setNeedDate(nest.getNeedDateTime());
            nestEntity.setNester(nest.getNester());
            nestEntity.setOptionId(nest.getOptionId());
            nestEntity.setSplitGroupCode(nest.getOptionId());
            nestEntity.setNestDxfUrl(nest.getDxfUrl());
            nestEntity.setBookSheet(nest.getBookSheet());
            nestEntity.setReportPdfUrl(nest.getReportPdfUrl());
            nestEntity.setCuttingProgramUrl(nest.getCuttingProgramUrl());
            nestEntity.setRate(nest.getRate()); // 利用率，钢板减去余料，再与零件重量进行计算，得到利用率
            nestEntity.setVersionBrief("V1");
            nestEntity.setPreVersion(preVersion);

            lantekNestNestMapper.insert(nestEntity);

            log.info("套料:{}", JsonUtils.toJsonString(nestEntity));

            // 零件
            List<LantekNestPart> parts = vo.getPart().stream()
                    .map(e -> {
                        LantekNestPart part = MkBeanUtils.copyProperties(e, LantekNestPart.class);
                        part.setNestId(vo.getNest().getNestId());
                        part.setNestPlanId(e.getPartPlanId());
                        part.setUniCode(e.getPartId());
                        part.setPartName(e.getPartName());
                        part.setQuantity(e.getQuantity());
                        part.setNetWeight(e.getNetWeight());
                        part.setArea(e.getArea());
                        part.setRectangleArea(e.getRectangleArea());
                        part.setRequireFactoryId(e.getFactoryCode());
                        part.setWidth(e.getWidth());
                        part.setLength(e.getLength());
                        part.setThickness(e.getThickness());
                        part.setPartMapUrl(e.getPngUrl());
                        part.setPlateCode("Pre_" + vo.getNest().getNestId());
                        part.setSortingCount(0);// 分拣数量
                        part.setPartId(e.getPartId().split("#")[0]);
                        part.setPreVersion(preVersion);

                        return part;
                    })
                    .collect(Collectors.toList());

            for (LantekNestPart part : parts) {
                partMap.computeIfAbsent(part.getNestPlanId(), kk -> new ArrayList<>()).add(part);
            }

            lantekNestPartMapper.insertBatchSomeColumn(parts);

            log.info("零件:{}", JsonUtils.toJsonString(parts));

            // 钢板
            List<LantekNestPlate> plates = vo.getPlate()
                    .stream()
                    .map(e -> {
                        LantekNestPlate plate = MkBeanUtils.copyProperties(e, LantekNestPlate.class);
                        plate.setAmount(BigDecimal.valueOf(1));
                        plate.setHeatNumber(e.getHeatId());
                        plate.setNestId(vo.getNest().getNestId());
                        plate.setStockListNo("Pre_" + vo.getNest().getNestId());
                        plate.setMaterielName("Pre_" + vo.getNest().getNestId());
                        plate.setFactoryIdk(e.getFactoryCode());
                        plate.setTexture(e.getTexture());
                        plate.setNorm(e.getThickness().toString());
                        plate.setWidth(e.getWidth());
                        plate.setLength(e.getLength());
                        plate.setStorehouseId(e.getStoreCode());
                        plate.setSequence(e.getSequence());
                        plate.setLayer(e.getSequence());
                        plate.setIsVirtual(true);
                        plate.setEmptyCutLength(e.getEmptyCutLength());
                        plate.setCutTime(e.getCutTime());
                        plate.setTotalCutLength(e.getTotalCutLength());
                        plate.setRate(vo.getNest().getRate());
                        plate.setHoleCount(e.getHoleCount());
                        plate.setSideLength(vo.getNest().getSideLength());
                        plate.setStatus(1);// 领料状态
                        plate.setPngUrl(e.getPngUrl());
                        plate.setPositionCode(e.getPositionCode());
                        plate.setPreVersion(preVersion);

                        return plate;
                    })
                    .collect(Collectors.toList());

            lantekNestPlateMapper.insertBatchSomeColumn(plates);

            log.info("钢板:{}", JsonUtils.toJsonString(plates));

            // 余料
            List<LantekNestExcess> excess = vo.getExcess()
                    .stream()
                    .map(e -> {
                        LantekNestExcess plate = MkBeanUtils.copyProperties(e, LantekNestExcess.class);
                        plate.setNestId(vo.getNest().getNestId());
                        plate.setFactoryIdk(e.getFactoryCode());
                        plate.setStockListNo("Pre_" + vo.getNest().getNestId());
                        plate.setExMaterielId(e.getExcessCode());
                        plate.setTexture(e.getTexture());
                        plate.setNorm(e.getThickness().toString());
                        plate.setWidth(e.getWidth());
                        plate.setLength(e.getLength());
                        plate.setWeight(e.getWeight());
                        plate.setOutStock(0);
                        plate.setPreVersion(preVersion);

                        return plate;
                    })
                    .collect(Collectors.toList());
            if (CollUtil.isNotEmpty(excess)) {
                lantekNestExcessMapper.insertBatchSomeColumn(excess);
            }

            log.info("余料:{}", JsonUtils.toJsonString(excess));

            // 走刀
            List<LantekNestMove> moves = vo.getMove()
                    .stream()
                    .map(e -> {
                        LantekNestMove move = MkBeanUtils.copyProperties(e, LantekNestMove.class);
                        move.setNestId(vo.getNest().getNestId());
                        move.setCutLength(e.getCutLength().multiply(BigDecimal.valueOf(1000)));
                        move.setFactoryIdk(e.getFactoryCode());
                        move.setMoveTime(e.getMoveTime());
                        move.setMoveType(e.getMoveType());
                        move.setHoleCount(e.getHoleCount());
                        move.setHoleTime(e.getHoleTime());
                        move.setTotalHoleTime(e.getTotalHoleTime());
                        move.setCutRate(e.getCutRate().multiply(BigDecimal.valueOf(1000)));
                        move.setTotalCutTime(e.getTotalCutTime());
                        move.setPreVersion(preVersion);

                        return move;
                    })
                    .collect(Collectors.toList());

            lantekNestMoveMapper.insertBatchSomeColumn(moves);

            // 更新计划信息
            for (String nestPlanId : partMap.keySet()) {
                LantekPushPlan one = lantekPushPlanMapper.lambdaQuery().eq(LantekPushPlan::getNestPlanId, nestPlanId).eq(LantekPushPlan::getPreVersion, preVersion).one();
                if (one == null) {
                    throw SyExceptionUtils.e("推送计划不存在，nestPlanId:{}", nestPlanId);
                }
                int sum = partMap.get(nestPlanId).stream().mapToInt(LantekNestPart::getQuantity).sum();

                BigDecimal cha = one.getPlanAmount()
                        .subtract(one.getPlanFinishAmount())
                        .subtract(new BigDecimal(sum));

                if (cha.compareTo(new BigDecimal(0)) == 0) {
                    one.setConsumeStatus(2);
                    one.setPlanFinishAmount(new BigDecimal(sum).add(one.getPlanFinishAmount()));
                } else if (cha.compareTo(new BigDecimal(0)) > 0) {
                    one.setConsumeStatus(1);
                    one.setPlanFinishAmount(new BigDecimal(sum).add(one.getPlanFinishAmount()));
                } else {
                    throw SyExceptionUtils.e("套料异常，零件{}，需要{}个，已套{}，待套{}，数量超了", one.getPartName(), one.getPlanAmount(), one.getPlanFinishAmount(), sum);
                }

                lantekPushPlanMapper.lambdaUpdate()
                        .eq(LantekPushPlan::getId, one.getId())
                        .set(LantekPushPlan::getConsumeStatus, one.getConsumeStatus())
                        .set(LantekPushPlan::getPlanFinishAmount, one.getPlanFinishAmount())
                        .update();

            }

        }

    }

    @Override
    public NestReceiveReqVo nestReceiveNew(String body) {
        return null;
    }

}
